import { isObject } from "./is/index";

export function deepMerge<T = any>(src: any = {}, target: any = {}): T {
	let key: string;
	for (key in target) {
		src[key] = isObject(src[key]) ? deepMerge(src[key], target[key]) : (src[key] = target[key]);
	}
	return src;
}
/**
 * 判断是否 url
 * */
export function isUrl(url: string) {
	return /^(http|https):\/\//g.test(url);
}
/**
 * 递归获得所有节点ID
 * @param rows
 * @returns
 */
export const getAllKeys = (rows: any): number[] => {
	let keys = [];
	for (let i = 0; i < rows.length; i++) {
		const row = rows[i];
		keys.push(row?.id);
		if (row?.children && row?.children.length > 0) {
			keys = keys.concat(getAllKeys(row?.children)); // 递归获取子级节点的 key 值
		}
	}
	return keys;
};
// 验证是否为blob格式
export function blobValidate(data: { type: string }) {
	return data.type !== "application/json";
}
// 输入文本提取出${}变量
export function extractPlaceholders(text: string, isKey: boolean = false) {
	const regex = /\{\{(\w+)\}\}/g;
	let varKeys = [];
	let keys = [];
	let match;
	while ((match = regex.exec(text)) !== null) {
		varKeys.push(match[0]); // 将匹配到的占位符保存到数组中
		if (isKey) {
			keys.push(match[1]);
		}
	}
	return isKey ? { varKeys: varKeys, keys: keys } : varKeys;
}
export function extractPlaceholdersFromHtml(html: string, isKey: boolean = false) {
	// const regex = /\${(\w+)}/g;
	const regex = /\{\{(\w+)\}\}/g;
	let varKeys = [];
	let keys = [];
	let textWithoutHtml = html.replace(/<[^>]*>/g, ""); // 去除 HTML 标签，只提取纯文本中的占位符
	let match;
	while ((match = regex.exec(textWithoutHtml)) !== null) {
		varKeys.push(match[0]); // 将匹配到的占位符保存到数组中
		if (isKey) {
			keys.push(match[1]);
		}
	}
	return isKey ? { varKeys: varKeys, keys: keys } : varKeys;
}
// 匹配 ${xxx} 格式的内容
export function containsPlaceholder(value: string) {
	const regex = /\{\{[^}]+\}\}/;
	return regex.test(value);
}
export function matchPlaceholder(value: string) {
	// 正则表达式来匹配 {{xxx}} 并提取其中的内容
	const regex = /\{\{(.*?)\}\}/;
	const match = value.match(regex);

	if (match) {
		// 获取匹配到的第一个子组，即 {{xxx}} 中的内容
		const extractedValue = match[1];
		return extractedValue; // 返回提取的内容
	} else {
		// 如果没有找到匹配的模式，返回空字符串
		return "";
	}
}

/**
 * 通用的辅助工具方法
 * @module 通用工具方法
 * */
// 获取数据类型
export function toRawType(value: any) {
	const _toString = Object.prototype.toString;
	return _toString.call(value).slice(8, -1);
}
// 转化样式布局值
export function converLayout(value: any, defaultValue = "100%") {
	// 是否为数字 ex："222"、222
	function isLooselyNumber(num: any) {
		if (toRawType(num) === "Number") return true;
		if (toRawType(num) === "String") {
			return !Number.isNaN(Number(num));
		}
		return false;
	}

	function isCssLength(str: string) {
		if (typeof str !== "string") return false;
		return str.match(/^([0-9])*(%|px|rem|em)$/i);
	}
	return isLooselyNumber(value) ? Number(value) : isCssLength(value) ? value : defaultValue;
}

/**
 * @description: 获取地址参数
 * @param {string} url 指定地址，默认取当前页地址
 * @return {string} { a: 1, b: 2, c: 3 }
 */
export function getQueryObject(url?: string): { [propName: string]: any } {
	url = url || window?.location.href || "";
	const questionIndex = url.lastIndexOf("?");
	const obj: { [propName: string]: any } = {};
	if (questionIndex > 0) {
		const search = url.substring(questionIndex + 1);
		const reg = /([^?&=]+)=([^?&=]*)/g;
		search.replace(reg, (rs, $1, $2) => {
			const name = decodeURIComponent($1);
			let val = decodeURIComponent($2);
			val = String(val);
			obj[name] = val;
			return rs;
		});
	}
	return obj;
}
/**
 * @description: 根据url解析出路由path路径
 * @param {string} url 默认取当前页面地址
 * @param {boolean} isIncludeParams 是否需要包含路由参数，便于路由跳转携带数据
 * @return {string}
 */
export function getRoutePath(url = "", isIncludeParams = false) {
	url = url || window.location.href;
	const divideStr = "/";
	const reg = new RegExp(`//[\\w-\\.:]+${divideStr}(.*)*`);
	const match = url.match(reg) || [];
	let pathWithParams = "/" + (match[1] || "");

	// 去除哈希部分
	const hashIndex = pathWithParams.indexOf("#");
	if (hashIndex !== -1) {
		pathWithParams = pathWithParams.substring(hashIndex + 1);
	}

	if (!isIncludeParams) {
		return pathWithParams;
	} else {
		const path = pathWithParams.split("?")[0];
		return path;
	}
}
